﻿using Cysharp.Threading.Tasks;
using YooAsset;
namespace Client.Base
{
    public class FsmInitPackage : PatchState
    {
        public FsmInitPackage(PatchProcess procedure) : base(procedure)
        {
        }

        public override async void OnEnter()
        {
            YooAssets.Initialize();
            var packages = YAPackageInfo.Setting.packages;
            for (int i = 0; i < packages.Length; i++)
                await InitPackage(packages[i]);
            Process.TryTransition<FsmRequestPackageVersion>();
        }


        private async UniTask InitPackage(YAPackage pk)
        {
            this.Log("[Patch] FsmInitPackage.");
            var playMode = Process.playMode;
            var package = YooAssets.TryGetPackage(pk.packageName);
            if (package == null) package = YooAssets.CreatePackage(pk.packageName);

            InitializationOperation initializationOperation = null;
            if (playMode == EPlayMode.EditorSimulateMode)
            {
                var buildResult = EditorSimulateModeHelper.SimulateBuild(pk.packageName);
                var packageRoot = buildResult.PackageRootDirectory;
                var createParameters = new EditorSimulateModeParameters();
                createParameters.EditorFileSystemParameters = FileSystemParameters.CreateDefaultEditorFileSystemParameters(packageRoot);
                initializationOperation = package.InitializeAsync(createParameters);
            }
            else if (playMode == EPlayMode.OfflinePlayMode)
            {
                var createParameters = new OfflinePlayModeParameters();
                if (!pk.isRaw)
                {
                    var decryption = new YAFileStreamDecryption();
                    createParameters.BuildinFileSystemParameters = FileSystemParameters.CreateDefaultBuildinFileSystemParameters(decryption);
                    createParameters.BuildinFileSystemParameters.AddParameter(FileSystemParametersDefine.MANIFEST_SERVICES, new YAProcessManifest());
                }
                else
                {
                    createParameters.BuildinFileSystemParameters = FileSystemParameters.CreateDefaultBuildinFileSystemParameters();
                }
                initializationOperation = package.InitializeAsync(createParameters);
            }
            else if (playMode == EPlayMode.HostPlayMode)
            {
                string remote = $"{YAPackageInfo.Setting.remoteURL}/{pk.packageName}/{YAPackageInfo.Setting.remoteVersion}";
                string defaultHostServer = remote;
                string fallbackHostServer = remote;
                IRemoteServices remoteServices = new RemoteServices(defaultHostServer, fallbackHostServer);
                var createParameters = new HostPlayModeParameters();
                if (!pk.isRaw)
                {
                    // 初始化资源包
                    var decryption = new YAFileStreamDecryption();
                    createParameters.BuildinFileSystemParameters = FileSystemParameters.CreateDefaultBuildinFileSystemParameters(decryption);
                    createParameters.BuildinFileSystemParameters.AddParameter(FileSystemParametersDefine.MANIFEST_SERVICES, new YAProcessManifest());
                    createParameters.CacheFileSystemParameters = FileSystemParameters.CreateDefaultCacheFileSystemParameters(remoteServices, decryption);
                }
                else
                {
                    createParameters.BuildinFileSystemParameters = FileSystemParameters.CreateDefaultBuildinFileSystemParameters();
                    createParameters.CacheFileSystemParameters = FileSystemParameters.CreateDefaultCacheFileSystemParameters(remoteServices);
                }

                initializationOperation = package.InitializeAsync(createParameters);
            }
            else if (playMode == EPlayMode.WebPlayMode)
            {
                string remote = $"{YAPackageInfo.Setting.remoteURL}/{pk.packageName}/{YAPackageInfo.Setting.remoteVersion}";
                string defaultHostServer = remote;
                string fallbackHostServer = remote;
                IRemoteServices remoteServices = new RemoteServices(defaultHostServer, fallbackHostServer);
                var initParameters = new WebPlayModeParameters();
                initParameters.WebRemoteFileSystemParameters = FileSystemParameters.CreateDefaultWebRemoteFileSystemParameters(remoteServices);
                initParameters.WebServerFileSystemParameters = FileSystemParameters.CreateDefaultWebServerFileSystemParameters();
                initializationOperation = package.InitializeAsync(initParameters);

            }
            await initializationOperation.ToUniTask();
        }



        public class RemoteServices : IRemoteServices
        {
            private readonly string _defaultHostServer;
            private readonly string _fallbackHostServer;

            public RemoteServices(string defaultHostServer, string fallbackHostServer)
            {
                _defaultHostServer = defaultHostServer;
                _fallbackHostServer = fallbackHostServer;
            }
            string IRemoteServices.GetRemoteMainURL(string fileName)
            {
                return $"{_defaultHostServer}/{fileName}";
            }
            string IRemoteServices.GetRemoteFallbackURL(string fileName)
            {
                return $"{_fallbackHostServer}/{fileName}";
            }
        }

    }
}

